package com.huilian.iotbox.admin.wap.service.impl;
import com.alibaba.fastjson.JSON;
import com.huilian.iotbox.admin.wap.dao.StatsDeviceDao;
import com.huilian.iotbox.admin.wap.service.*;
import com.huilian.iotbox.data.common.ServerResponse;
import com.huilian.iotbox.data.dto.*;
import com.huilian.iotbox.data.enums.*;
import com.huilian.iotbox.data.po.MerchantStore;
import com.huilian.iotbox.data.po.StatsDevice;
import com.huilian.iotbox.data.service.StatsDeviceCommonService;
import com.huilian.iotbox.data.utils.DateTimeUtils;
import com.huilian.iotbox.data.vo.*;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;
import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.*;
import java.util.concurrent.ExecutionException;
import java.util.stream.Collectors;

/**
 * @author 龙 路 飞
 * @CreateDate: 2021-09-23 15:31
 * @Description:
 */
@Slf4j
@Service
public class StatsDeviceServiceImpl implements StatsDeviceService {

    @Autowired
    private OrderService orderService;
    @Autowired
    private DeviceService deviceService;
    @Resource
    private StatsDeviceDao statsDeviceDao;
    @Autowired
    private MerchantStoreService merchantStoreService;
    @Autowired
    private StatsDeviceCommonService statsDeviceCommonService;
    @Autowired
    private CommodityStockRecordService commodityStockRecordService;
    @Autowired
    private StatsCommodityStockRecordService statsCommodityStockRecordService;
    @Autowired
    private StatsStoreDeviceTypeService statsStoreDeviceTypeService;

    /**
     * 设备分析-小程序端
     *
     * @param statsDeviceDto
     * @return
     */
    @Override
    public ServerResponse findAllSumStatsDeviceSumByApplet(StatsDeviceDto statsDeviceDto) throws ExecutionException, InterruptedException {
        if (StringUtils.isEmpty(statsDeviceDto.getMchStoreId())) {
            return ServerResponse.createByErrorMessage("缺少参数");
        }

        String error = "error";
        String result = Optional.ofNullable(statsDeviceDto)
                .map(statsStoreDto1 -> statsDeviceDto.getMchStoreId())
                .map(statsStoreDto1 -> statsDeviceDto.getStartYMD())
                .map(statsStoreDto1 -> statsDeviceDto.getEndYMD())
                .orElse("error");

        if (error.equals(result)) {
            return ServerResponse.createByErrorMessage("缺少参数");
        }

        final String toDayDateYMD = DateTimeUtils.getCurrTime();

        // 当天的实时统计数据
        List<StatsDeviceVo> todayStatsDeviceList = new ArrayList<>();
        Map<String, StatsDeviceVo> todayStatsDeviceMap = new HashMap<>();

        DeviceDto deviceDto = new DeviceDto();
        deviceDto.setUserInfo(statsDeviceDto.getUserInfo());
        deviceDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
        ServerResponse serverResponse = deviceService.findDevice(deviceDto);
        if (!serverResponse.getIsSuccess()) {
            return serverResponse;
        }
        List<DeviceVo> deviceList = (List<DeviceVo>) serverResponse.getData();

        Map<String, DeviceVo> deviceMap = new HashMap<>();
        if (deviceList.size() > 0) {
            deviceMap = deviceList.stream().collect(Collectors.toMap(DeviceVo::getDeviceNo, a -> a, (k1, k2) -> k1));
        }

        StatsDeviceDto statsDevice = new StatsDeviceDto();
        statsDevice.setType(1);
        statsDevice.setMchStoreId(statsDeviceDto.getMchStoreId());
        statsDevice.setStartYMD(statsDeviceDto.getStartYMD());
        statsDevice.setEndYMD(statsDeviceDto.getEndYMD());
        List<StatsDeviceVo> sumStatsDeviceVoByDeviceNoList = statsDeviceDao.findStatsDeviceSumByMchStoreId(statsDevice);
        Map<String, StatsDeviceVo> sumStatsDeviceVoByDeviceNoMap = new HashMap<>();

        if (sumStatsDeviceVoByDeviceNoList.size() > 0) {
            sumStatsDeviceVoByDeviceNoMap = sumStatsDeviceVoByDeviceNoList.stream().collect(Collectors.toMap(StatsDeviceVo::getDeviceNo, a -> a, (k1, k2) -> k1));
        }

        for (StatsDeviceVo statsDeviceVo : sumStatsDeviceVoByDeviceNoList) {
            StatsDeviceVo vo = todayStatsDeviceMap.get(statsDeviceVo.getDeviceNo());
            if (StringUtils.isEmpty(vo)) {
                vo = new StatsDeviceVo();
                vo.setTurnover(BigDecimal.ZERO);
                vo.setTurnoverOnLine(BigDecimal.ZERO);
                vo.setTurnoverOffline(BigDecimal.ZERO);
                vo.setOnLineCoinCount(0);
                vo.setOffLineCoinCount(0);
                vo.setGiftConsume(0);
                vo.setGiftCost(BigDecimal.ZERO);
                vo.setInsertCoinTotal(0);
                vo.setConsumeCount(0);
                vo.setOneYuanDenomination(0);
                vo.setFiveYuanDenomination(0);
                vo.setTenYuanDenomination(0);
                vo.setTwentyYuanDenomination(0);
                vo.setFiftyYuanDenomination(0);
                vo.setOneHundredYuanDenomination(0);
            }

            DeviceVo deviceVo = deviceMap.get(statsDeviceVo.getDeviceNo());
            if (!StringUtils.isEmpty(deviceVo)) {
                statsDeviceVo.setAlias(deviceVo.getAlias());
                statsDeviceVo.setRemarkName(deviceVo.getRemarkName());
                statsDeviceVo.setDeviceTypeName(deviceVo.getDeviceTypeName());
                statsDeviceVo.setDeviceTypeId(deviceVo.getDeviceTypeId());
            }

            statsDeviceVo.setTurnover(statsDeviceVo.getTurnover().add(vo.getTurnover()));
            statsDeviceVo.setTurnoverOnLine(statsDeviceVo.getTurnoverOnLine().add(vo.getTurnoverOnLine()));
            statsDeviceVo.setTurnoverOffline(statsDeviceVo.getTurnoverOffline().add(vo.getTurnoverOffline()));
            statsDeviceVo.setOnLineCoinCount(statsDeviceVo.getOnLineCoinCount() + vo.getOnLineCoinCount());
            statsDeviceVo.setOffLineCoinCount(statsDeviceVo.getOffLineCoinCount() + vo.getOffLineCoinCount());
            statsDeviceVo.setGiftConsume(statsDeviceVo.getGiftConsume() + vo.getGiftConsume());
            statsDeviceVo.setGiftCost(statsDeviceVo.getGiftCost().add(vo.getGiftCost()));
            statsDeviceVo.setInsertCoinTotal(statsDeviceVo.getOnLineCoinCount() + statsDeviceVo.getOffLineCoinCount());
            statsDeviceVo.setConsumeCount(statsDeviceVo.getConsumeCount() + vo.getConsumeCount());
            statsDeviceVo.setOneYuanDenomination(statsDeviceVo.getOneYuanDenomination() + vo.getOneYuanDenomination());
            statsDeviceVo.setFiveYuanDenomination(statsDeviceVo.getFiveYuanDenomination() + vo.getFiveYuanDenomination());
            statsDeviceVo.setTenYuanDenomination(statsDeviceVo.getTenYuanDenomination() + vo.getTenYuanDenomination());
            statsDeviceVo.setTwentyYuanDenomination(statsDeviceVo.getTwentyYuanDenomination() + vo.getTwentyYuanDenomination());
            statsDeviceVo.setFiftyYuanDenomination(statsDeviceVo.getFiftyYuanDenomination() + vo.getFiftyYuanDenomination());
            statsDeviceVo.setOneHundredYuanDenomination(statsDeviceVo.getOneHundredYuanDenomination() + vo.getOneHundredYuanDenomination());
            statsDeviceVo.setOutCoinTotal(statsDeviceVo.getOutCoinTotal() + vo.getOutCoinTotal());
            statsDeviceVo.setFetchMemberOutCoinTotal(statsDeviceVo.getFetchMemberOutCoinTotal() + vo.getFetchMemberOutCoinTotal());

            Integer consumeRecordInsertCoinCount = statsDeviceVo.getConsumeCount();
            BigDecimal rate = BigDecimal.ZERO;
            if (consumeRecordInsertCoinCount != 0) {
                rate = new BigDecimal(String.valueOf(statsDeviceVo.getGiftConsume())).divide(new BigDecimal(String.valueOf(consumeRecordInsertCoinCount)), 4, BigDecimal.ROUND_HALF_UP);
            } else if (consumeRecordInsertCoinCount == 0 && statsDeviceVo.getGiftConsume().compareTo(0) == 1) {
                // 投币次数为0，但有出礼
                rate = BigDecimal.valueOf(1);
            }
            BigDecimal percentage = rate.multiply(new BigDecimal("100"));
            statsDeviceVo.setGiftOutRate(percentage);
        }

        // 排序
        if (sumStatsDeviceVoByDeviceNoList.size() > 0) {
            // 营收排序
            sumStatsDeviceVoByDeviceNoList = sumStatsDeviceVoByDeviceNoList.stream().sorted((item1, item2) -> {
                if (statsDeviceDto.getTurnoverSort()) {
                    return item1.getTurnover().compareTo(item2.getTurnover());
                } else {
                    return item2.getTurnover().compareTo(item1.getTurnover());
                }
            }).collect(Collectors.toList());
        }

        //总营业额
        BigDecimal turnover = BigDecimal.ZERO;
        //线上投币
        Integer insertCoinOnLine = 0;
        //线下投币
        Integer insertCoinOffline = 0;
        //礼品消耗数
        Integer giftConsume = 0;

        // 统计该场地总营业额
        for (DeviceVo deviceVo : deviceList) {
            StatsDeviceVo statsDeviceVo = sumStatsDeviceVoByDeviceNoMap.get(deviceVo.getDeviceNo());
            if (StringUtils.isEmpty(statsDeviceVo)) {
                continue;
            }
            turnover = turnover.add(statsDeviceVo.getTurnover());
            insertCoinOnLine += statsDeviceVo.getOnLineCoinCount();
            insertCoinOffline += statsDeviceVo.getOffLineCoinCount();
            giftConsume += statsDeviceVo.getGiftConsume();
        }

        MerchantStoreDto merchantStoreDto = new MerchantStoreDto();
        merchantStoreDto.setId(statsDeviceDto.getMchStoreId());
        merchantStoreDto.setUserInfo(statsDeviceDto.getUserInfo());
        MerchantStore store = merchantStoreService.findOneMerchantStoreById(merchantStoreDto);
        StatsDeviceVo statsDeviceTotalVo = new StatsDeviceVo();
        statsDeviceTotalVo.setStoreName(store.getStoreName());
        statsDeviceTotalVo.setTurnover(turnover);
        statsDeviceTotalVo.setOnLineCoinCount(insertCoinOnLine);
        statsDeviceTotalVo.setOffLineCoinCount(insertCoinOffline);
        statsDeviceTotalVo.setGiftConsume(giftConsume);
        statsDeviceTotalVo.setStatsDeviceVoList(sumStatsDeviceVoByDeviceNoList);

        return ServerResponse.createBySuccess(statsDeviceTotalVo);
    }

    @Override
    public List<StatsStoreVo> findStatsDeviceByMerchantStoreIdArray(StatsStoreDto statsStoreDto) {
        return statsDeviceDao.findStatsDeviceByMerchantStoreIdArray(statsStoreDto);
    }

    public static void main(String[] args) {
        System.out.println(0 / 12);
    }


    /**
     * 统计兑币机每个面额收了多少次
     *
     * @param deviceVo
     * @param startTime
     * @param endTime
     * @param statsDevice
     */
    private void statsDeviceDenomination(DeviceVo deviceVo, String startTime, String endTime, StatsDevice statsDevice) {
        Integer[] deviceTypeIdArray = new Integer[]{
                DeviceTypeEnum.SUPER_MONEY_CHANGER.getCode(),
                DeviceTypeEnum.CONVERTIBLE_CURRENCY_MACHINE.getCode()
        };
        String[] channelTypeArray = new String[]{
                ChannelTypeEnum.BILL_MACHINE.getCode(),
                ChannelTypeEnum.COIN_BOX.getCode()
        };
        Integer[] orderStatusArray = new Integer[]{
                OrderStatusEnum.SUCCESS.getCode(),
                OrderStatusEnum.PART_REFUND.getCode(),
                OrderStatusEnum.FULL_FERUND.getCode(),
                OrderStatusEnum.REFUNDING.getCode(),
        };


        OrderDto orderDenomination = new OrderDto();
        orderDenomination.setDeviceNo(deviceVo.getDeviceNo());
        orderDenomination.setStartTime(startTime);
        orderDenomination.setEndTime(endTime);
        orderDenomination.setMchType(MchTypeEnum.CASH_RECEIPTS.getCode());
        orderDenomination.setDeviceTypeIdArray(deviceTypeIdArray);
        orderDenomination.setChannelTypeArray(channelTypeArray);
        orderDenomination.setOrderStatusArray(orderStatusArray);
        List<OrderVo> orderVoList = orderService.findDenominationCountByDeviceNo(orderDenomination);

        if (orderVoList.size() > 0) {
            statsDeviceCommonService.statsDeviceDenomination(orderVoList, statsDevice);
        }
    }

    /**
     * 查询设备统计,用来展示在table表格里面
     */
    @Override
    public List<StatsDeviceVo> findStatsDeviceTableList(StatsDeviceDto statsDeviceDto) {
        List<StatsDeviceVo> list = new ArrayList<>();

        GiftIncrementDto giftIncrementDto = new GiftIncrementDto();
        giftIncrementDto.setUserInfo(statsDeviceDto.getUserInfo());
        giftIncrementDto.setStartTime(DateTimeUtils.getTodayStartTime());
        giftIncrementDto.setEndTime(DateTimeUtils.getTodayEndTime());
        giftIncrementDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
        giftIncrementDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());

        ConsumeRecordDto consumeRecordDto = new ConsumeRecordDto();
        consumeRecordDto.setUserInfo(statsDeviceDto.getUserInfo());
        consumeRecordDto.setStartTime(DateTimeUtils.getTodayStartTime());
        consumeRecordDto.setEndTime(DateTimeUtils.getTodayEndTime());
        consumeRecordDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
        consumeRecordDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
        consumeRecordDto.setStatus(ConsumeRecordStatusEnum.SUCCESS.getCode());


        if (statsDeviceDto.getDayType() == 0) {
            // 当天
            List<GiftIncrementVo> giftIncrementList = new ArrayList<>();
            List<ConsumeRecordVo> consumeRecordList = new ArrayList<>();
            // 使用Map集合可以避免双重循环提高效率
            Map<String, GiftIncrementVo> giftIncrementMap = giftIncrementList.stream().collect(Collectors.toMap(v -> v.getDeviceId() + "" + v.getHierarchy() + v.getFreightLane(), v -> v));
            for (ConsumeRecordVo consumeRecordVo : consumeRecordList) {
                StatsDeviceVo statsDeviceVo = new StatsDeviceVo();
                GiftIncrementVo giftIncrementVo = giftIncrementMap.get(consumeRecordVo.getDeviceId() + "" + consumeRecordVo.getHierarchy() + consumeRecordVo.getFreightLane());
                if (ObjectUtils.isEmpty(giftIncrementVo)) {
                    giftIncrementVo = new GiftIncrementVo();
                    giftIncrementVo.setTuiLiIncrementTotal(0);
                    giftIncrementVo.setTotalCostPrice(BigDecimal.ZERO);
                }

                statsDeviceVo.setDeviceAlias(consumeRecordVo.getDeviceAlias());
                statsDeviceVo.setDeviceTypeName(consumeRecordVo.getDeviceTypeName());
                statsDeviceVo.setDeviceId(consumeRecordVo.getDeviceId());
                statsDeviceVo.setDeviceNo(consumeRecordVo.getDeviceNo());
                statsDeviceVo.setInsertCoinTotal(consumeRecordVo.getOffLineCoinCount() + consumeRecordVo.getOnLineCoinCount());
                statsDeviceVo.setGiftConsume(giftIncrementVo.getTuiLiIncrementTotal());
                statsDeviceVo.setGiftCost(giftIncrementVo.getTotalCostPrice());

                statsDeviceVo.setOnLineCoinCount(consumeRecordVo.getOnLineCoinCount());
                statsDeviceVo.setOffLineCoinCount(consumeRecordVo.getOffLineCoinCount());


                //普通订单
                OrderDto orderDto = new OrderDto();
                orderDto.setUserInfo(statsDeviceDto.getUserInfo());
                orderDto.setStartTime(DateTimeUtils.getTodayStartTime());
                orderDto.setEndTime(DateTimeUtils.getTodayEndTime());
                orderDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
                orderDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
                orderDto.setDeviceNo(consumeRecordVo.getDeviceNo());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    orderDto.setHierarchy(consumeRecordVo.getHierarchy());
                    orderDto.setFreightLane(consumeRecordVo.getFreightLane());
                }

                //活动订单
                ActivityOrderDto activityOrderDto = new ActivityOrderDto();
                activityOrderDto.setUserInfo(statsDeviceDto.getUserInfo());
                activityOrderDto.setStartTime(DateTimeUtils.getTodayStartTime());
                activityOrderDto.setEndTime(DateTimeUtils.getTodayEndTime());
                activityOrderDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
                activityOrderDto.setDeviceNo(consumeRecordVo.getDeviceNo());
                activityOrderDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    activityOrderDto.setHierarchy(consumeRecordVo.getHierarchy());
                    activityOrderDto.setFreightLane(consumeRecordVo.getFreightLane());
                }


                ConsumeRecordDto consumeRecordCount = new ConsumeRecordDto();
                consumeRecordCount.setUserInfo(statsDeviceDto.getUserInfo());
                consumeRecordCount.setStartTime(DateTimeUtils.getTodayStartTime());
                consumeRecordCount.setEndTime(DateTimeUtils.getTodayEndTime());
                consumeRecordCount.setMerchantStoreId(statsDeviceDto.getMchStoreId());
                consumeRecordCount.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
                consumeRecordCount.setDeviceNo(consumeRecordVo.getDeviceNo());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    consumeRecordCount.setHierarchy(consumeRecordVo.getHierarchy());
                    consumeRecordCount.setFreightLane(consumeRecordVo.getFreightLane());
                }

                statsDeviceVo.setConsumeCount(0);

                statsDeviceVo.setOnLinePayOutCoinTotal(consumeRecordVo.getOnLinePayOutCoinTotal());
                statsDeviceVo.setOffLinePayOutCoinTotal(consumeRecordVo.getOffLinePayOutCoinTotal());
                statsDeviceVo.setWeiXinSeckillOutCoinTotal(consumeRecordVo.getWeiXinSeckillOutCoinTotal());
                statsDeviceVo.setWeiXinVoucherOutCoinTotal(consumeRecordVo.getWeiXinVoucherOutCoinTotal());
                statsDeviceVo.setWeiXinGroupBuyingOutCoinTotal(consumeRecordVo.getWeiXinGroupBuyingOutCoinTotal());
                statsDeviceVo.setDouYinOutCoinTotal(consumeRecordVo.getDouYinOutCoinTotal());
                statsDeviceVo.setMeiTuanOutCoinTotal(consumeRecordVo.getMeiTuanOutCoinTotal());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    statsDeviceVo.setHierarchy(consumeRecordVo.getHierarchy());
                    statsDeviceVo.setFreightLane(consumeRecordVo.getFreightLane());
                }

                list.add(statsDeviceVo);
            }
            log.info("list：" + JSON.toJSONString(list));
        } else if (statsDeviceDto.getDayType() == -1) {
            // 自定义日期范围
            statsDeviceDto.setType(1);
            //根据日期范围查询
            if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                list = statsDeviceDao.findStatsDeviceTableListV2(statsDeviceDto);
            } else {
                list = statsDeviceDao.findStatsDeviceTableList(statsDeviceDto);
            }

            if (statsDeviceDto.getEndDateStr().equals(DateTimeUtils.getCurrentDateStr())) {
                List<GiftIncrementVo> giftIncrementList = new ArrayList<>();
                List<ConsumeRecordVo> consumeRecordList = new ArrayList<>();
                list = this.toAdd(list, giftIncrementList, consumeRecordList, statsDeviceDto);
            }
        } else {
            switch (statsDeviceDto.getDayType()) {
                case 1:
                    // 昨天
                    statsDeviceDto.setStartDateStr(DateTimeUtils.getYesterday());
                    statsDeviceDto.setEndDateStr(DateTimeUtils.getYesterday());
                    statsDeviceDto.setType(1);
                    if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                        list = statsDeviceDao.findStatsDeviceTableListV2(statsDeviceDto);
                    } else {
                        list = statsDeviceDao.findStatsDeviceTableList(statsDeviceDto);
                    }
                    break;
                case 2:
                    // 本周
                    statsDeviceDto.setStartDateStr(DateTimeUtils.getWeekFirstDay());
                    statsDeviceDto.setEndDateStr(DateTimeUtils.getCurrTime());
                    statsDeviceDto.setType(1);
                    //根据日期范围查询
                    if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                        list = statsDeviceDao.findStatsDeviceTableListV2(statsDeviceDto);
                    } else {
                        list = statsDeviceDao.findStatsDeviceTableList(statsDeviceDto);
                    }
                    if (statsDeviceDto.getEndDateStr().equals(DateTimeUtils.getCurrentDateStr())) {
                        List<GiftIncrementVo> giftIncrementList = new ArrayList<>();
                        List<ConsumeRecordVo> consumeRecordList = new ArrayList<>();
                        list = this.toAdd(list, giftIncrementList, consumeRecordList, statsDeviceDto);
                    }
                    break;
                case 3:
                    //本月
                    statsDeviceDto.setStartDateStr(DateTimeUtils.getMonthFirstDay());
                    statsDeviceDto.setEndDateStr(DateTimeUtils.getCurrTime());
                    statsDeviceDto.setType(1);
                    //根据日期范围查询
                    if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                        list = statsDeviceDao.findStatsDeviceTableListV2(statsDeviceDto);
                    } else {
                        list = statsDeviceDao.findStatsDeviceTableList(statsDeviceDto);
                    }
                    if (statsDeviceDto.getEndDateStr().equals(DateTimeUtils.getCurrentDateStr())) {
                        List<GiftIncrementVo> giftIncrementList = new ArrayList<>();
                        List<ConsumeRecordVo> consumeRecordList = new ArrayList<>();
                        list = this.toAdd(list, giftIncrementList, consumeRecordList, statsDeviceDto);
                    }
                    break;
                case 4:
                    // 今年
                    statsDeviceDto.setStartDateStr(DateTimeUtils.getYearFirstDayTimeYMD());
                    statsDeviceDto.setEndDateStr(DateTimeUtils.getCurrTime());
                    statsDeviceDto.setType(1);
                    //根据日期范围查询
                    if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                        list = statsDeviceDao.findStatsDeviceTableListV2(statsDeviceDto);
                    } else {
                        list = statsDeviceDao.findStatsDeviceTableList(statsDeviceDto);
                    }
                    if (statsDeviceDto.getEndDateStr().equals(DateTimeUtils.getCurrentDateStr())) {
                        List<GiftIncrementVo> giftIncrementList = new ArrayList<>();
                        List<ConsumeRecordVo> consumeRecordList = new ArrayList<>();
                        list = this.toAdd(list, giftIncrementList, consumeRecordList, statsDeviceDto);
                    }
                    break;
                case 5:
                    //上月
                    //根据日期范围查询
                    statsDeviceDto.setStartDateStr(DateTimeUtils.getPreviousMonthFirstDay());
                    statsDeviceDto.setEndDateStr(DateTimeUtils.getPreviousMonthLastDay());
                    statsDeviceDto.setType(2);
                    if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                        list = statsDeviceDao.findStatsDeviceTableListV2(statsDeviceDto);
                    } else {
                        list = statsDeviceDao.findStatsDeviceTableList(statsDeviceDto);
                    }
                    break;
                default:
                    break;
            }
        }
        DeviceDto deviceDto = new DeviceDto();
        deviceDto.setUserInfo(statsDeviceDto.getUserInfo());
        if (!ObjectUtils.isEmpty(statsDeviceDto.getMchStoreId()) && statsDeviceDto.getMchStoreId() != -1) {
            deviceDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
        }
        if (!ObjectUtils.isEmpty(statsDeviceDto.getDeviceTypeId()) && statsDeviceDto.getDeviceTypeId() != -1) {
            deviceDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
        }
        ServerResponse serverResponse = null;
        if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
            serverResponse = deviceService.findDevice_v3(deviceDto);
        } else {
            serverResponse = deviceService.findDevice_v2(deviceDto);
        }
        if (!serverResponse.getIsSuccess()) {
            return list;
        }
        List<DeviceVo> deviceList = (List<DeviceVo>) serverResponse.getData();
        // 使用Map集合可以避免双重循环提高效率
        Map<String, StatsDeviceVo> statsDeviceMap = null;
        if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
            statsDeviceMap = list.stream().collect(Collectors.toMap(v -> v.getDeviceId() + "" + v.getHierarchy() + v.getFreightLane(), v -> v));
        } else {
            statsDeviceMap = list.stream().collect(Collectors.toMap(v -> v.getDeviceId() + "", v -> v));
        }

        List<StatsDeviceVo> returnList = new ArrayList<>();
        // 所有设备都要查询出来,这段代码是把有值的设备赋值一下
        for (DeviceVo deviceVo : deviceList) {
            StatsDeviceVo statsDeviceVo = null;
            if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                statsDeviceVo = statsDeviceMap.get(deviceVo.getId() + "" + deviceVo.getHierarchy() + deviceVo.getFreightLane());
            } else {
                statsDeviceVo = statsDeviceMap.get(deviceVo.getId() + "");
            }

            if (ObjectUtils.isEmpty(statsDeviceVo)) {
                statsDeviceVo = new StatsDeviceVo();
            }
            statsDeviceVo.setDeviceAlias(deviceVo.getAlias());
            statsDeviceVo.setDeviceTypeName(statsDeviceVo.getDeviceTypeName());
            statsDeviceVo.setDeviceId(statsDeviceVo.getDeviceId());
            statsDeviceVo.setDeviceNo(deviceVo.getDeviceNo());
            statsDeviceVo.setInsertCoinTotal(!ObjectUtils.isEmpty(statsDeviceVo.getInsertCoinTotal()) ? statsDeviceVo.getInsertCoinTotal() : 0);
            statsDeviceVo.setGiftConsume(!ObjectUtils.isEmpty(statsDeviceVo.getGiftConsume()) ? statsDeviceVo.getGiftConsume() : 0);
            statsDeviceVo.setGiftCost(!ObjectUtils.isEmpty(statsDeviceVo.getGiftCost()) ? statsDeviceVo.getGiftCost() : BigDecimal.ZERO);
            statsDeviceVo.setTurnover(!ObjectUtils.isEmpty(statsDeviceVo.getTurnover()) ? statsDeviceVo.getTurnover() : BigDecimal.ZERO);

            statsDeviceVo.setTurnoverOnLine(!ObjectUtils.isEmpty(statsDeviceVo.getTurnoverOnLine()) ? statsDeviceVo.getTurnoverOnLine() : BigDecimal.ZERO);
            statsDeviceVo.setTurnoverOffline(!ObjectUtils.isEmpty(statsDeviceVo.getTurnoverOffline()) ? statsDeviceVo.getTurnoverOffline() : BigDecimal.ZERO);
            statsDeviceVo.setTurnoverDouYin(!ObjectUtils.isEmpty(statsDeviceVo.getTurnoverDouYin()) ? statsDeviceVo.getTurnoverDouYin() : BigDecimal.ZERO);
            statsDeviceVo.setTurnoverMeiTuan(!ObjectUtils.isEmpty(statsDeviceVo.getTurnoverMeiTuan()) ? statsDeviceVo.getTurnoverMeiTuan() : BigDecimal.ZERO);
            statsDeviceVo.setSeckillMoney(!ObjectUtils.isEmpty(statsDeviceVo.getSeckillMoney()) ? statsDeviceVo.getSeckillMoney() : BigDecimal.ZERO);
            statsDeviceVo.setGroupBookingMoney(!ObjectUtils.isEmpty(statsDeviceVo.getGroupBookingMoney()) ? statsDeviceVo.getGroupBookingMoney() : BigDecimal.ZERO);
            statsDeviceVo.setConsumptionOfRedEnvelopesMoney(!ObjectUtils.isEmpty(statsDeviceVo.getConsumptionOfRedEnvelopesMoney()) ? statsDeviceVo.getConsumptionOfRedEnvelopesMoney() : BigDecimal.ZERO);
            statsDeviceVo.setMemberOfTheStoredValueMoney(!ObjectUtils.isEmpty(statsDeviceVo.getMemberOfTheStoredValueMoney()) ? statsDeviceVo.getMemberOfTheStoredValueMoney() : BigDecimal.ZERO);


            statsDeviceVo.setOnLineCoinCount(!ObjectUtils.isEmpty(statsDeviceVo.getOnLineCoinCount()) ? statsDeviceVo.getOnLineCoinCount() : 0);
            statsDeviceVo.setOffLineCoinCount(!ObjectUtils.isEmpty(statsDeviceVo.getOffLineCoinCount()) ? statsDeviceVo.getOffLineCoinCount() : 0);
            statsDeviceVo.setConsumeCount(!ObjectUtils.isEmpty(statsDeviceVo.getConsumeCount()) ? statsDeviceVo.getConsumeCount() : 0);
            statsDeviceVo.setOnLinePayOutCoinTotal(!ObjectUtils.isEmpty(statsDeviceVo.getOnLinePayOutCoinTotal()) ? statsDeviceVo.getOnLinePayOutCoinTotal() : 0);
            statsDeviceVo.setOffLinePayOutCoinTotal(!ObjectUtils.isEmpty(statsDeviceVo.getOffLinePayOutCoinTotal()) ? statsDeviceVo.getOffLinePayOutCoinTotal() : 0);
            statsDeviceVo.setWeiXinSeckillOutCoinTotal(!ObjectUtils.isEmpty(statsDeviceVo.getWeiXinSeckillOutCoinTotal()) ? statsDeviceVo.getWeiXinSeckillOutCoinTotal() : 0);
            statsDeviceVo.setWeiXinGroupBuyingOutCoinTotal(!ObjectUtils.isEmpty(statsDeviceVo.getWeiXinGroupBuyingOutCoinTotal()) ? statsDeviceVo.getWeiXinGroupBuyingOutCoinTotal() : 0);
            statsDeviceVo.setWeiXinVoucherOutCoinTotal(!ObjectUtils.isEmpty(statsDeviceVo.getWeiXinVoucherOutCoinTotal()) ? statsDeviceVo.getWeiXinVoucherOutCoinTotal() : 0);
            statsDeviceVo.setDouYinOutCoinTotal(!ObjectUtils.isEmpty(statsDeviceVo.getDouYinOutCoinTotal()) ? statsDeviceVo.getDouYinOutCoinTotal() : 0);
            statsDeviceVo.setMeiTuanOutCoinTotal(!ObjectUtils.isEmpty(statsDeviceVo.getMeiTuanOutCoinTotal()) ? statsDeviceVo.getMeiTuanOutCoinTotal() : 0);
            statsDeviceVo.setFreightLane(deviceVo.getFreightLane());
            statsDeviceVo.setHierarchy(deviceVo.getHierarchy());
            statsDeviceVo = this.countInsertCoinTotalFormat(statsDeviceVo);
            returnList.add(statsDeviceVo);
        }
        // 排序
        returnList.sort(Comparator.comparing(k -> ObjectUtils.isEmpty(k.getDeviceAlias()) ? 99999 : k.getDeviceAlias(), Comparator.naturalOrder()));
        return returnList;
    }

    @Override
    public List<StatsDeviceVo> findStatsSalesDeviceTableList(StatsDeviceDto statsDeviceDto) {
        statsDeviceDto.setFirstType(CommodityStockRecordFirstTypeEnum.OUTBOUND.getCode());
        statsDeviceDto.setSecondaryType(CommodityStockRecordSecondTypeEnum.VENDING_MACHINE_OUT.getCode());
        List<StatsDeviceVo> list = new ArrayList<>();
        CommodityStockRecordDto commodityStockRecordDto = new CommodityStockRecordDto();
        commodityStockRecordDto.setUserInfo(statsDeviceDto.getUserInfo());
        commodityStockRecordDto.setStartTime(DateTimeUtils.getTodayStartTime());
        commodityStockRecordDto.setEndTime(DateTimeUtils.getTodayEndTime());
        commodityStockRecordDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
        commodityStockRecordDto.setFirstType(CommodityStockRecordFirstTypeEnum.OUTBOUND.getCode());
        commodityStockRecordDto.setSecondaryType(CommodityStockRecordSecondTypeEnum.VENDING_MACHINE_OUT.getCode());
        if (statsDeviceDto.getDayType() == 0) {
            List<CommodityStockRecordVo> dayList = commodityStockRecordService.findStatsCommodityStockRecordList(commodityStockRecordDto);
            for (CommodityStockRecordVo commodityStockRecordVo : dayList) {
                StatsDeviceVo statsDeviceVo = new StatsDeviceVo();
                statsDeviceVo.setDeviceAlias(commodityStockRecordVo.getDeviceAlias());
                statsDeviceVo.setDeviceTypeName(commodityStockRecordVo.getDeviceTypeName());
                statsDeviceVo.setDeviceId(commodityStockRecordVo.getDeviceId());
                statsDeviceVo.setTotalQuantity(commodityStockRecordVo.getTotalQuantity());
                statsDeviceVo.setDeviceNo(commodityStockRecordVo.getDeviceNo());
                statsDeviceVo.setTotalRetailPrice(commodityStockRecordVo.getTotalRetailPrice());
                statsDeviceVo.setTotalCostPrice(commodityStockRecordVo.getTotalCostPrice());
                statsDeviceVo.setProfit(commodityStockRecordVo.getTotalRetailPrice().subtract(commodityStockRecordVo.getTotalCostPrice()));
                list.add(statsDeviceVo);
            }
        } else if (statsDeviceDto.getDayType() == -1) {
            //根据自定义日期查询，有可能包含当天
            statsDeviceDto.setType(1);
            list = statsCommodityStockRecordService.findStatsCommodityStockRecordDeviceTableList(statsDeviceDto);
            //包含当天数据
            if (statsDeviceDto.getEndDateStr().equals(DateTimeUtils.getCurrentDateStr())) {
                List<CommodityStockRecordVo> dayList = commodityStockRecordService.findStatsCommodityStockRecordList(commodityStockRecordDto);
                //当天数据和其他日期数据合拼
                list = this.toAddCommodityStockRecord(list, dayList);
            }
        } else {
            switch (statsDeviceDto.getDayType()) {
                case 1:
                    //昨天
                    statsDeviceDto.setStartDateStr(DateTimeUtils.getYesterday());
                    statsDeviceDto.setEndDateStr(DateTimeUtils.getYesterday());
                    statsDeviceDto.setType(1);
                    list = statsCommodityStockRecordService.findStatsCommodityStockRecordDeviceTableList(statsDeviceDto);
                    break;
                case 3:
                    //本月
                    list = this.getThisMonthStatsCommodityStockRecord(statsDeviceDto, commodityStockRecordDto);
                    break;
                case 4:
                    //今年
                    statsDeviceDto.setStartDateStr(DateTimeUtils.getYearFirstDayTimeYM());
                    statsDeviceDto.setEndDateStr(DateTimeUtils.getMonthYM());
                    statsDeviceDto.setType(2);
                    List<StatsDeviceVo> yearList = statsCommodityStockRecordService.findStatsCommodityStockRecordDeviceTableList(statsDeviceDto);
                    //本月
                    list = this.getThisMonthStatsCommodityStockRecord(statsDeviceDto, commodityStockRecordDto);
                    //合拼数据
                    list = this.toAddCommodityStockRecord2(yearList, list);
                    break;
                case 5:
                    //上月
                    statsDeviceDto.setStartDateStr(DateTimeUtils.getPreviousMonthYM());
                    statsDeviceDto.setEndDateStr(DateTimeUtils.getPreviousMonthYM());
                    statsDeviceDto.setType(2);
                    list = statsCommodityStockRecordService.findStatsCommodityStockRecordDeviceTableList(statsDeviceDto);
                    break;
                default:
                    break;
            }
        }
        DeviceDto deviceDto = new DeviceDto();
        deviceDto.setUserInfo(statsDeviceDto.getUserInfo());
        if (!ObjectUtils.isEmpty(statsDeviceDto.getMchStoreId()) && statsDeviceDto.getMchStoreId() != -1) {
            deviceDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
        }
        //查询售货机设备
        ServerResponse serverResponse = deviceService.findSalesDevice(deviceDto);
        if (!serverResponse.getIsSuccess()) {
            return list;
        }
        List<DeviceVo> deviceList = (List<DeviceVo>) serverResponse.getData();
        // 使用Map集合可以避免双重循环提高效率
        Map<Integer, StatsDeviceVo> statsDeviceMap = list.stream().collect(Collectors.toMap(StatsDeviceVo::getDeviceId, v -> v));
        log.info("list转map：" + JSON.toJSONString(statsDeviceMap));
        List<StatsDeviceVo> returnList = new ArrayList<>();
        // 所有设备都要查询出来,这段代码是把有值的设备赋值一下
        for (DeviceVo deviceVo : deviceList) {
            log.info("设备号：" + deviceVo.getSalesDeviceNo());
            StatsDeviceVo statsDeviceVo = statsDeviceMap.get(deviceVo.getId());
            log.info("获取数据：" + statsDeviceVo);
            if (ObjectUtils.isEmpty(statsDeviceVo)) {
                statsDeviceVo = new StatsDeviceVo();
            }
            statsDeviceVo.setDeviceAlias(deviceVo.getAlias());
            statsDeviceVo.setDeviceTypeName(statsDeviceVo.getDeviceTypeName());
            statsDeviceVo.setDeviceId(statsDeviceVo.getDeviceId());
            statsDeviceVo.setDeviceNo(deviceVo.getSalesDeviceNo());
            statsDeviceVo.setTotalQuantity(!ObjectUtils.isEmpty(statsDeviceVo.getTotalQuantity()) ? statsDeviceVo.getTotalQuantity() : 0);
            statsDeviceVo.setTotalRetailPrice(!ObjectUtils.isEmpty(statsDeviceVo.getTotalRetailPrice()) ? statsDeviceVo.getTotalRetailPrice() : BigDecimal.ZERO);
            statsDeviceVo.setProfit(!ObjectUtils.isEmpty(statsDeviceVo.getProfit()) ? statsDeviceVo.getProfit() : BigDecimal.ZERO);
            returnList.add(statsDeviceVo);
        }
        return returnList;
    }

    private List<StatsDeviceVo> toAddCommodityStockRecord2(List<StatsDeviceVo> statsDeviceList, List<StatsDeviceVo> list) {
        // 使用Map集合可以避免双重循环提高效率
        Map<Integer, StatsDeviceVo> commodityStockRecordMap =
                list.stream().collect(Collectors.toMap(StatsDeviceVo::getDeviceId, v -> v));
        for (StatsDeviceVo statsDeviceVo : statsDeviceList) {
            StatsDeviceVo statsDeviceVo1 = commodityStockRecordMap.get(statsDeviceVo.getDeviceId());
            if (ObjectUtils.isEmpty(statsDeviceVo1)) {
                statsDeviceVo1 = new StatsDeviceVo();
                statsDeviceVo1.setTotalQuantity(0);
                statsDeviceVo1.setTotalCostPrice(BigDecimal.ZERO);
                statsDeviceVo1.setTotalRetailPrice(BigDecimal.ZERO);
            }
            statsDeviceVo.setTotalQuantity(statsDeviceVo1.getTotalQuantity() + statsDeviceVo.getTotalQuantity());
            log.info("当天的{}，",statsDeviceVo1.getTotalCostPrice());
            log.info("别天的{}，",statsDeviceVo.getTotalCostPrice());
            statsDeviceVo.setTotalCostPrice(statsDeviceVo1.getTotalCostPrice().add(statsDeviceVo.getTotalCostPrice()));
            statsDeviceVo.setTotalRetailPrice(statsDeviceVo1.getTotalRetailPrice().add(statsDeviceVo.getTotalRetailPrice()));
            //利润 = 总售价 - 总成本
            statsDeviceVo.setProfit(statsDeviceVo.getTotalRetailPrice().subtract(statsDeviceVo.getTotalCostPrice()));
        }
        return statsDeviceList;
    }

    private List<StatsDeviceVo> toAddCommodityStockRecord(List<StatsDeviceVo> statsDeviceList, List<CommodityStockRecordVo> dayList) {
        // 使用Map集合可以避免双重循环提高效率
        Map<Integer, CommodityStockRecordVo> commodityStockRecordMap =
                dayList.stream().collect(Collectors.toMap(CommodityStockRecordVo::getDeviceId, v -> v));
        for (StatsDeviceVo statsDeviceVo : statsDeviceList) {
            CommodityStockRecordVo commodityStockRecordVo = commodityStockRecordMap.get(statsDeviceVo.getDeviceId());
            if (ObjectUtils.isEmpty(commodityStockRecordVo)) {
                commodityStockRecordVo = new CommodityStockRecordVo();
                commodityStockRecordVo.setTotalQuantity(0);
                commodityStockRecordVo.setTotalCostPrice(BigDecimal.ZERO);
                commodityStockRecordVo.setTotalRetailPrice(BigDecimal.ZERO);
            }
            statsDeviceVo.setTotalQuantity(commodityStockRecordVo.getTotalQuantity() + statsDeviceVo.getTotalQuantity());
            statsDeviceVo.setTotalCostPrice(commodityStockRecordVo.getTotalCostPrice().add(statsDeviceVo.getTotalCostPrice()));
            statsDeviceVo.setTotalRetailPrice(commodityStockRecordVo.getTotalRetailPrice().add(statsDeviceVo.getTotalRetailPrice()));
            //利润 = 总售价 - 总成本
            statsDeviceVo.setProfit(statsDeviceVo.getTotalRetailPrice().subtract(statsDeviceVo.getTotalCostPrice()));
        }
        return statsDeviceList;
    }

    private List<StatsDeviceVo> getThisMonthStatsCommodityStockRecord(StatsDeviceDto statsDeviceDto, CommodityStockRecordDto commodityStockRecordDto) {
        //本月
        statsDeviceDto.setStartDateStr(DateTimeUtils.getMonthFirstDay());
        statsDeviceDto.setEndDateStr(DateTimeUtils.getCurrTime());
        statsDeviceDto.setType(1);
        List<StatsDeviceVo> list = statsCommodityStockRecordService.findStatsCommodityStockRecordDeviceTableList(statsDeviceDto);
        //当天
        List<CommodityStockRecordVo> dayList = commodityStockRecordService.findStatsCommodityStockRecordList(commodityStockRecordDto);
        list = this.toAddCommodityStockRecord(list, dayList);
        return list;
    }

    /**
     * 本方法专门查当天数据
     * 用于包含当天的日期范围
     */
    public List<StatsDeviceVo> toAdd(List<StatsDeviceVo> statsDeviceList, List<GiftIncrementVo> giftIncrementList, List<ConsumeRecordVo> consumeRecordList, StatsDeviceDto statsDeviceDto) {
        // 使用Map集合可以避免双重循环提高效率
        Map<String, GiftIncrementVo> giftIncrementMap = giftIncrementList.stream().collect(Collectors.toMap(v -> v.getDeviceId() + "" + v.getHierarchy() + v.getFreightLane(), v -> v));
        Map<String, ConsumeRecordVo> consumeRecordMap = consumeRecordList.stream()
                .collect(Collectors.toMap(v -> v.getDeviceId() + "" + v.getHierarchy() + v.getFreightLane(), v -> v));
        for (StatsDeviceVo statsDeviceVo : statsDeviceList) {
            GiftIncrementVo giftIncrementVo = giftIncrementMap.get(statsDeviceVo.getDeviceId() + "" + statsDeviceVo.getHierarchy() + statsDeviceVo.getFreightLane());
            if (ObjectUtils.isEmpty(giftIncrementVo)) {
                giftIncrementVo = new GiftIncrementVo();
                giftIncrementVo.setTuiLiIncrementTotal(0);
                giftIncrementVo.setTotalCostPrice(BigDecimal.ZERO);
            }
            if (statsDeviceVo.getFreightLane() == null) {
                statsDeviceVo.setFreightLane(0);
            }
            if (statsDeviceVo.getHierarchy() == null) {
                statsDeviceVo.setHierarchy(0);
            }
            ConsumeRecordVo consumeRecordVo = consumeRecordMap.get(statsDeviceVo.getDeviceId() + "" + statsDeviceVo.getHierarchy() + statsDeviceVo.getFreightLane());
            if (ObjectUtils.isEmpty(consumeRecordVo)) {
                consumeRecordVo = new ConsumeRecordVo();
                consumeRecordVo.setOffLineCoinCount(0);
                consumeRecordVo.setOnLineCoinCount(0);
            } else {
                OrderDto orderDto = new OrderDto();
                orderDto.setUserInfo(statsDeviceDto.getUserInfo());
                orderDto.setStartTime(DateTimeUtils.getTodayStartTime());
                orderDto.setEndTime(DateTimeUtils.getTodayEndTime());
                orderDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
                orderDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
                orderDto.setDeviceNo(statsDeviceVo.getDeviceNo());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    orderDto.setHierarchy(consumeRecordVo.getHierarchy());
                    orderDto.setFreightLane(consumeRecordVo.getFreightLane());
                }

                //活动订单
                ActivityOrderDto activityOrderDto = new ActivityOrderDto();
                activityOrderDto.setUserInfo(statsDeviceDto.getUserInfo());
                activityOrderDto.setStartTime(DateTimeUtils.getTodayStartTime());
                activityOrderDto.setEndTime(DateTimeUtils.getTodayEndTime());
                activityOrderDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
                activityOrderDto.setDeviceNo(statsDeviceVo.getDeviceNo());
                activityOrderDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    activityOrderDto.setHierarchy(consumeRecordVo.getHierarchy());
                    activityOrderDto.setFreightLane(consumeRecordVo.getFreightLane());
                }

                ConsumeRecordDto consumeRecordDto = new ConsumeRecordDto();
                consumeRecordDto.setUserInfo(statsDeviceDto.getUserInfo());
                consumeRecordDto.setStartTime(statsDeviceDto.getStartDateStr());
                consumeRecordDto.setEndTime(statsDeviceDto.getEndDateStr());
                consumeRecordDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
                consumeRecordDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
                consumeRecordDto.setDeviceNo(statsDeviceVo.getDeviceNo());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    consumeRecordDto.setHierarchy(consumeRecordVo.getHierarchy());
                    consumeRecordDto.setFreightLane(consumeRecordVo.getFreightLane());
                }
            }

            statsDeviceVo.setGiftConsume(statsDeviceVo.getGiftConsume() + giftIncrementVo.getTuiLiIncrementTotal());
            statsDeviceVo.setGiftCost(statsDeviceVo.getGiftCost().add(giftIncrementVo.getTotalCostPrice()));

            statsDeviceVo.setInsertCoinTotal(statsDeviceVo.getInsertCoinTotal() + (consumeRecordVo.getOffLineCoinCount() + consumeRecordVo.getOnLineCoinCount()));
            statsDeviceVo.setOnLineCoinCount(statsDeviceVo.getOnLineCoinCount() + consumeRecordVo.getOnLineCoinCount());
            statsDeviceVo.setOffLineCoinCount(statsDeviceVo.getOffLineCoinCount() + consumeRecordVo.getOffLineCoinCount());

            statsDeviceVo.setOnLinePayOutCoinTotal(statsDeviceVo.getOnLinePayOutCoinTotal() + (!ObjectUtils.isEmpty(consumeRecordVo.getOnLinePayOutCoinTotal()) ? consumeRecordVo.getOnLinePayOutCoinTotal() : 0));
            statsDeviceVo.setOffLinePayOutCoinTotal(statsDeviceVo.getOffLinePayOutCoinTotal() + (!ObjectUtils.isEmpty(consumeRecordVo.getOffLinePayOutCoinTotal()) ? consumeRecordVo.getOffLinePayOutCoinTotal() : 0));
            statsDeviceVo.setWeiXinSeckillOutCoinTotal(statsDeviceVo.getWeiXinSeckillOutCoinTotal() + (!ObjectUtils.isEmpty(consumeRecordVo.getWeiXinSeckillOutCoinTotal()) ? consumeRecordVo.getWeiXinSeckillOutCoinTotal() : 0));
            statsDeviceVo.setWeiXinVoucherOutCoinTotal(statsDeviceVo.getWeiXinVoucherOutCoinTotal() + (!ObjectUtils.isEmpty(consumeRecordVo.getWeiXinVoucherOutCoinTotal()) ? consumeRecordVo.getWeiXinVoucherOutCoinTotal() : 0));
            statsDeviceVo.setWeiXinGroupBuyingOutCoinTotal(statsDeviceVo.getWeiXinGroupBuyingOutCoinTotal() + (!ObjectUtils.isEmpty(consumeRecordVo.getWeiXinGroupBuyingOutCoinTotal()) ? consumeRecordVo.getWeiXinGroupBuyingOutCoinTotal() : 0));
            statsDeviceVo.setDouYinOutCoinTotal(statsDeviceVo.getDouYinOutCoinTotal() + (!ObjectUtils.isEmpty(consumeRecordVo.getDouYinOutCoinTotal()) ? consumeRecordVo.getDouYinOutCoinTotal() : 0));
            statsDeviceVo.setMeiTuanOutCoinTotal(statsDeviceVo.getMeiTuanOutCoinTotal() + (!ObjectUtils.isEmpty(consumeRecordVo.getMeiTuanOutCoinTotal()) ? consumeRecordVo.getMeiTuanOutCoinTotal() : 0));

//            statsDeviceVo.setHierarchy(consumeRecordVo.getHierarchy());
//            statsDeviceVo.setFreightLane(consumeRecordVo.getFreightLane());
//            consumeRecordMap.remove(statsDeviceVo.getDeviceId() + "" + statsDeviceVo.getHierarchy() + statsDeviceVo.getFreightLane());
//            consumeRecordList.remove(consumeRecordVo);
        }


        if (!consumeRecordList.isEmpty()) {
            for (Map.Entry<String, ConsumeRecordVo> entry : consumeRecordMap.entrySet()) {
                StatsDeviceVo statsDeviceVo = new StatsDeviceVo();
                ConsumeRecordVo consumeRecord = entry.getValue();
                GiftIncrementVo giftIncrementVo = giftIncrementMap.get(consumeRecord.getDeviceId() + "" + consumeRecord.getHierarchy() + consumeRecord.getFreightLane());

                OrderDto orderDto = new OrderDto();
                orderDto.setUserInfo(statsDeviceDto.getUserInfo());
                orderDto.setStartTime(DateTimeUtils.getTodayStartTime());
                orderDto.setEndTime(DateTimeUtils.getTodayEndTime());
                orderDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
                orderDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
                orderDto.setDeviceNo(consumeRecord.getDeviceNo());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    orderDto.setHierarchy(consumeRecord.getHierarchy());
                    orderDto.setFreightLane(consumeRecord.getFreightLane());
                }
                
                //活动订单
                ActivityOrderDto activityOrderDto = new ActivityOrderDto();
                activityOrderDto.setUserInfo(statsDeviceDto.getUserInfo());
                activityOrderDto.setStartTime(DateTimeUtils.getTodayStartTime());
                activityOrderDto.setEndTime(DateTimeUtils.getTodayEndTime());
                activityOrderDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
                activityOrderDto.setDeviceNo(consumeRecord.getDeviceNo());
                activityOrderDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    activityOrderDto.setHierarchy(consumeRecord.getHierarchy());
                    activityOrderDto.setFreightLane(consumeRecord.getFreightLane());
                }

                ConsumeRecordDto consumeRecordDto = new ConsumeRecordDto();
                consumeRecordDto.setUserInfo(statsDeviceDto.getUserInfo());
                consumeRecordDto.setStartTime(statsDeviceDto.getStartDateStr());
                consumeRecordDto.setEndTime(statsDeviceDto.getEndDateStr());
                consumeRecordDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
                consumeRecordDto.setDeviceTypeId(statsDeviceDto.getDeviceTypeId());
                consumeRecordDto.setDeviceNo(consumeRecord.getDeviceNo());
                if (statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.ONE_TO_MANY_BOXES.getCode()) || statsDeviceDto.getDeviceTypeId().equals(DeviceTypeEnum.GASHAPON_MACHINE.getCode())) {
                    consumeRecordDto.setHierarchy(consumeRecord.getHierarchy());
                    consumeRecordDto.setFreightLane(consumeRecord.getFreightLane());
                }
                statsDeviceVo.setDeviceAlias(consumeRecord.getDeviceAlias());
                statsDeviceVo.setDeviceTypeName(consumeRecord.getDeviceTypeName());
                statsDeviceVo.setDeviceId(consumeRecord.getDeviceId());
                statsDeviceVo.setDeviceNo(consumeRecord.getDeviceNo());
                statsDeviceVo.setInsertCoinTotal(consumeRecord.getOffLineCoinCount() + consumeRecord.getOnLineCoinCount());
                if (giftIncrementMap.containsKey(consumeRecord.getDeviceId() + "" + consumeRecord.getHierarchy() + consumeRecord.getFreightLane())) {
                    statsDeviceVo.setGiftConsume(giftIncrementVo.getTuiLiIncrementTotal());
                    statsDeviceVo.setGiftCost(giftIncrementVo.getTotalCostPrice());
                } else {
                    statsDeviceVo.setGiftConsume(0);
                    statsDeviceVo.setGiftCost(BigDecimal.ZERO);
                }

                statsDeviceVo.setOnLineCoinCount(consumeRecord.getOnLineCoinCount());
                statsDeviceVo.setOffLineCoinCount(consumeRecord.getOffLineCoinCount());

                statsDeviceVo.setOnLinePayOutCoinTotal(consumeRecord.getOnLinePayOutCoinTotal());
                statsDeviceVo.setOffLinePayOutCoinTotal(consumeRecord.getOffLinePayOutCoinTotal());
                statsDeviceVo.setWeiXinSeckillOutCoinTotal(consumeRecord.getWeiXinSeckillOutCoinTotal());
                statsDeviceVo.setWeiXinVoucherOutCoinTotal(consumeRecord.getWeiXinVoucherOutCoinTotal());
                statsDeviceVo.setWeiXinGroupBuyingOutCoinTotal(consumeRecord.getWeiXinGroupBuyingOutCoinTotal());
                statsDeviceVo.setDouYinOutCoinTotal(consumeRecord.getDouYinOutCoinTotal());
                statsDeviceVo.setMeiTuanOutCoinTotal(consumeRecord.getMeiTuanOutCoinTotal());

                statsDeviceVo.setHierarchy(consumeRecord.getHierarchy());
                statsDeviceVo.setFreightLane(consumeRecord.getFreightLane());
                statsDeviceList.add(statsDeviceVo);
            }
        }
        return statsDeviceList;
    }

    /**
     * 计算出礼比例
     */
    public StatsDeviceVo countInsertCoinTotalFormat(StatsDeviceVo statsDeviceVo) {
        if (statsDeviceVo.getGiftConsume() >= statsDeviceVo.getInsertCoinTotal() && statsDeviceVo.getInsertCoinTotal() > 0) {
            statsDeviceVo.setInsertCoinTotalFormat(1);
            statsDeviceVo.setGiftConsumeFormat(statsDeviceVo.getGiftConsume() / statsDeviceVo.getInsertCoinTotal());
        } else if (statsDeviceVo.getInsertCoinTotal() >= statsDeviceVo.getGiftConsume() && statsDeviceVo.getGiftConsume() > 0) {
            statsDeviceVo.setInsertCoinTotalFormat(statsDeviceVo.getInsertCoinTotal() / statsDeviceVo.getGiftConsume());
            statsDeviceVo.setGiftConsumeFormat(1);
        } else {
            statsDeviceVo.setInsertCoinTotalFormat(statsDeviceVo.getInsertCoinTotal());
            statsDeviceVo.setGiftConsumeFormat(statsDeviceVo.getGiftConsume());
        }
        return statsDeviceVo;
    }

    @Override
    public ServerResponse findStatsStoreDeviceByApplet(StatsDeviceDto statsDeviceDto) {
        List<StatsStoreDeviceTypeVo> statsStoreDeviceTypeVoList = new ArrayList<>();
        String error = "error";
        String result = Optional.ofNullable(statsDeviceDto)
                .map(statsDeviceDto1 -> statsDeviceDto.getMchStoreId())
                .map(statsDeviceDto1 -> statsDeviceDto.getDayType())
                .map(statsDeviceDto1 -> statsDeviceDto.getStartDateStr())
                .map(statsDeviceDto1 -> statsDeviceDto.getEndDateStr())
                .orElse("error");
        if (error.equals(result)) {
            return ServerResponse.createByErrorMessage("缺少参数");
        }
        //根据场地查询设备
        DeviceDto deviceDto = new DeviceDto();
        deviceDto.setUserInfo(statsDeviceDto.getUserInfo());
        deviceDto.setMerchantStoreId(statsDeviceDto.getMchStoreId());
        ServerResponse serverResponse = deviceService.findDevice_v2(deviceDto);
        if (!serverResponse.getIsSuccess()) {
            return serverResponse;
        }
        List<DeviceVo> deviceList = (List<DeviceVo>) serverResponse.getData();
        if (ObjectUtils.isEmpty(deviceList) || deviceList.size() == 0) {
            return ServerResponse.createByErrorMessage("暂无设备");
        }
        statsDeviceDto.setDeviceVoList(deviceList);
        try {
            if (statsDeviceDto.getDayType().compareTo(StatsDayTypeEnum.TODAY.getCode()) == 0) {
                statsStoreDeviceTypeVoList = this.findTodayStatsDeviceStoreFromOrder(statsDeviceDto);
            } else if (statsDeviceDto.getDayType().compareTo(StatsDayTypeEnum.CUSTOM_TIME.getCode()) == 0) {
                statsDeviceDto.setType(StatisticsTypeEnum.DAY.getCode());
                statsDeviceDto.setStartTime(statsDeviceDto.getStartDateStr());
                statsDeviceDto.setEndTime(DateTimeUtils.getYesterday());
                statsStoreDeviceTypeVoList = this.findFromStatsStoreDeviceNo(statsDeviceDto);
                //包含了当天
                if (statsDeviceDto.getEndDateStr().equals(DateTimeUtils.getCurrentDateStr())) {
                    List<StatsStoreDeviceTypeVo> todayStatsDeviceStoreFromOrder = this.findTodayStatsDeviceStoreFromOrder(statsDeviceDto);
                    this.statsStoreDeviceListAdd(statsStoreDeviceTypeVoList, todayStatsDeviceStoreFromOrder);
                }
            } else if (statsDeviceDto.getDayType().compareTo(StatsDayTypeEnum.YESTERDAY.getCode()) == 0) {
                //昨天
                statsDeviceDto.setStartTime(DateTimeUtils.getYesterday());
                statsDeviceDto.setEndTime(DateTimeUtils.getYesterday());
                statsDeviceDto.setType(StatisticsTypeEnum.DAY.getCode());
                statsStoreDeviceTypeVoList = this.findFromStatsStoreDeviceNo(statsDeviceDto);
            } else if (statsDeviceDto.getDayType().compareTo(StatsDayTypeEnum.THIS_MONTH.getCode()) == 0) {
                //本月
                statsDeviceDto.setStartTime(DateTimeUtils.getMonthFirstDay());
                statsDeviceDto.setEndTime(DateTimeUtils.getCurrTime());
                statsStoreDeviceTypeVoList = this.getThisMonthDevice(statsDeviceDto);
            } else if (statsDeviceDto.getDayType().compareTo(StatsDayTypeEnum.LAST_MONTH.getCode()) == 0) {
                //上月
                statsDeviceDto.setStartTime(DateTimeUtils.getPreviousMonthYM());
                statsDeviceDto.setEndTime(DateTimeUtils.getPreviousMonthYM());
                statsDeviceDto.setType(StatisticsTypeEnum.MONTH.getCode());
                statsStoreDeviceTypeVoList = this.findFromStatsStoreDeviceNo(statsDeviceDto);
            } else if (statsDeviceDto.getDayType().compareTo(StatsDayTypeEnum.THIS_YEAR.getCode()) == 0) {
                //今年
                statsDeviceDto.setStartTime(DateTimeUtils.getYearFirstDayTimeYM());
                statsDeviceDto.setEndTime(DateTimeUtils.getMonthYM());
                statsDeviceDto.setType(StatisticsTypeEnum.MONTH.getCode());
                statsStoreDeviceTypeVoList = this.findFromStatsStoreDeviceNo(statsDeviceDto);

                statsDeviceDto.setStartTime(DateTimeUtils.getMonthFirstDay());
                statsDeviceDto.setEndTime(DateTimeUtils.getCurrTime());
                List<StatsStoreDeviceTypeVo> thisMonthStatsStoreDeviceVoList = this.getThisMonthDevice(statsDeviceDto);
                this.statsStoreDeviceListAdd(statsStoreDeviceTypeVoList, thisMonthStatsStoreDeviceVoList);
            } else {
                throw new RuntimeException("缺少日期分支");
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return ServerResponse.createBySuccess(statsStoreDeviceTypeVoList.stream()
                .sorted((o1, o2) -> o2.getTurnover().compareTo(o1.getTurnover())) // 降序排序
                .collect(Collectors.toList()));
    }

    @Override
    public StatsStoreVo findStatsStoreByDeviceNo(StatsStoreDto storeDto) {
        return statsDeviceDao.findStatsStoreByDeviceNo(storeDto);
    }

    private List<StatsStoreDeviceTypeVo> getThisMonthDevice(StatsDeviceDto statsDeviceDto) {
        statsDeviceDto.setType(StatisticsTypeEnum.DAY.getCode());
        List<StatsStoreDeviceTypeVo> statsStoreDeviceNoList = this.findFromStatsStoreDeviceNo(statsDeviceDto);
        //当天
        List<StatsStoreDeviceTypeVo> todayStatsDeviceStoreList = this.findTodayStatsDeviceStoreFromOrder(statsDeviceDto);
        this.statsStoreDeviceListAdd(statsStoreDeviceNoList, todayStatsDeviceStoreList);
        return statsStoreDeviceNoList;
    }

    private void statsStoreDeviceListAdd(List<StatsStoreDeviceTypeVo> statsStoreDeviceNoList, List<StatsStoreDeviceTypeVo> todayStatsDeviceStoreList) {
        // 使用Map集合可以避免双重循环提高效率
        Map<String, StatsStoreDeviceTypeVo> statsStoreDeviceTypeVoMap = todayStatsDeviceStoreList.stream().collect(Collectors.toMap(StatsStoreDeviceTypeVo::getDeviceNo, v -> v));
        for (StatsStoreDeviceTypeVo storeDeviceTypeVo : statsStoreDeviceNoList) {
            log.info("设备号{}：", storeDeviceTypeVo.getDeviceNo());
            StatsStoreDeviceTypeVo statsStoreDeviceTypeVo = statsStoreDeviceTypeVoMap.get(storeDeviceTypeVo.getDeviceNo());
            if (StringUtils.isEmpty(statsStoreDeviceTypeVo)) {
                statsStoreDeviceTypeVo = new StatsStoreDeviceTypeVo();
                initStoreDeviceTypeData(statsStoreDeviceTypeVo);
            }
            storeDeviceTypeVo.setActivityTurnover(statsStoreDeviceTypeVo.getActivityTurnover().add(storeDeviceTypeVo.getActivityTurnover()));
            storeDeviceTypeVo.setScanCodePayTotalTurnover(statsStoreDeviceTypeVo.getScanCodePayTotalTurnover().add(storeDeviceTypeVo.getScanCodePayTotalTurnover()));
            storeDeviceTypeVo.setTurnoverMeiTuan(statsStoreDeviceTypeVo.getTurnoverMeiTuan().add(storeDeviceTypeVo.getTurnoverMeiTuan()));
            storeDeviceTypeVo.setTurnoverDouYin(statsStoreDeviceTypeVo.getTurnoverDouYin().add(storeDeviceTypeVo.getTurnoverDouYin()));
            storeDeviceTypeVo.setCashMoney(statsStoreDeviceTypeVo.getCashMoney().add(storeDeviceTypeVo.getCashMoney()));
            storeDeviceTypeVo.setGiftConsume(statsStoreDeviceTypeVo.getGiftConsume() + storeDeviceTypeVo.getGiftConsume());
            log.info("当天现金购币{}：",statsStoreDeviceTypeVo.getTotalQuantity());
            log.info("昨天现金购币{}：",storeDeviceTypeVo.getTotalQuantity());
            storeDeviceTypeVo.setTotalQuantity(statsStoreDeviceTypeVo.getTotalQuantity() + storeDeviceTypeVo.getTotalQuantity());
            storeDeviceTypeVo.setOnLinePayOutCoinTotal(statsStoreDeviceTypeVo.getOnLinePayOutCoinTotal() + storeDeviceTypeVo.getOnLinePayOutCoinTotal());
            storeDeviceTypeVo.setOffLinePayOutCoinTotal(statsStoreDeviceTypeVo.getOffLinePayOutCoinTotal() + storeDeviceTypeVo.getOffLinePayOutCoinTotal());
            storeDeviceTypeVo.setDouYinOutCoinTotal(statsStoreDeviceTypeVo.getDouYinOutCoinTotal() + storeDeviceTypeVo.getDouYinOutCoinTotal());
            storeDeviceTypeVo.setMeiTuanOutCoinTotal(statsStoreDeviceTypeVo.getMeiTuanOutCoinTotal() + storeDeviceTypeVo.getMeiTuanOutCoinTotal());
            storeDeviceTypeVo.setFetchMemberOutCoinTotal(statsStoreDeviceTypeVo.getFetchMemberOutCoinTotal() + storeDeviceTypeVo.getFetchMemberOutCoinTotal());
            log.info("当天现金购币{}：", statsStoreDeviceTypeVo.getWeiXinVerifyTotalCoin());
            log.info("昨天现金购币{}：", storeDeviceTypeVo.getWeiXinVerifyTotalCoin());
            storeDeviceTypeVo.setWeiXinVerifyTotalCoin(statsStoreDeviceTypeVo.getWeiXinVerifyTotalCoin() + storeDeviceTypeVo.getWeiXinVerifyTotalCoin());
            // 投币合计 = 线上投币 + 线下投币
            storeDeviceTypeVo.setInsertCoinTotal(statsStoreDeviceTypeVo.getInsertCoinTotal() + storeDeviceTypeVo.getInsertCoinTotal());
            // 线上投币
            storeDeviceTypeVo.setInsertCoinOnLine(statsStoreDeviceTypeVo.getInsertCoinOnLine() + storeDeviceTypeVo.getInsertCoinOnLine());
            // 线下投币
            storeDeviceTypeVo.setInsertCoinOffline(statsStoreDeviceTypeVo.getInsertCoinOffline() + storeDeviceTypeVo.getInsertCoinOffline());
            this.outConDevicePercent(storeDeviceTypeVo);
        }
    }

    private void outConDevicePercent(StatsStoreDeviceTypeVo storeDeviceTypeVo) {
        //初始化
        BigDecimal rate = new BigDecimal(0);
        storeDeviceTypeVo.setPercentOffLinePayOutCoin(rate);
        storeDeviceTypeVo.setPercentFetchMemberOutCoin(rate);
        storeDeviceTypeVo.setPercentOnLinePayOutCoinTotal(rate);
        storeDeviceTypeVo.setPercentOnLinePayOutCoinTotal(rate);
        storeDeviceTypeVo.setPercentArtificialOutCoin(rate);
        storeDeviceTypeVo.setPercentMeiTuanOutCoin(rate);
        storeDeviceTypeVo.setPercentDouYinOutCoin(rate);
        storeDeviceTypeVo.setPercentWeiXinVerifyOutCoin(rate);
        storeDeviceTypeVo.setPercentInsertCoinOffline(rate);
        storeDeviceTypeVo.setPercentInsertCoinOnLine(rate);
        //出币总数
        if (storeDeviceTypeVo.getOutCoinTotal() > 0) {
            //BigDecimal total = new BigDecimal(statsStoreVo.getOutCoinTotal());
            BigDecimal total = new BigDecimal(storeDeviceTypeVo.getOutCoinTotal());
            // 现金出币 除以 总出币 保留两位小数 乘 100
            BigDecimal offLinePayOutCoinTotal = new BigDecimal(storeDeviceTypeVo.getOffLinePayOutCoinTotal());
            BigDecimal offLinePayOutCoinTotalRate = offLinePayOutCoinTotal.divide(total, 2, BigDecimal.ROUND_HALF_UP);
            storeDeviceTypeVo.setPercentOffLinePayOutCoin(offLinePayOutCoinTotalRate.multiply(new BigDecimal("100")));

            //线上出币
            BigDecimal linePayOutCoinTotal = new BigDecimal(storeDeviceTypeVo.getOnLinePayOutCoinTotal());
            BigDecimal linePayOutCoinTotalRate = linePayOutCoinTotal.divide(total, 2, BigDecimal.ROUND_HALF_UP);
            storeDeviceTypeVo.setPercentOnLinePayOutCoinTotal(linePayOutCoinTotalRate.multiply(new BigDecimal("100")));

            //会员取币
            BigDecimal fetchMemberOutCoinTotal = new BigDecimal(storeDeviceTypeVo.getFetchMemberOutCoinTotal());
            BigDecimal fetchMemberOutCoinTotalRate = fetchMemberOutCoinTotal.divide(total, 2, BigDecimal.ROUND_HALF_UP);
            storeDeviceTypeVo.setPercentFetchMemberOutCoin(fetchMemberOutCoinTotalRate.multiply(new BigDecimal("100")));

            //抖音核销出币
            BigDecimal douYinOutCoinTotal = new BigDecimal(storeDeviceTypeVo.getDouYinOutCoinTotal());
            BigDecimal douYinOutCoinTotalRate = douYinOutCoinTotal.divide(total, 2, BigDecimal.ROUND_HALF_UP);
            storeDeviceTypeVo.setPercentDouYinOutCoin(douYinOutCoinTotalRate.multiply(new BigDecimal("100")));

            //美团核销出币
            BigDecimal meiTuanOutCoinTotal = new BigDecimal(storeDeviceTypeVo.getMeiTuanOutCoinTotal());
            BigDecimal meiTuanOutCoinTotalRate = meiTuanOutCoinTotal.divide(total, 2, BigDecimal.ROUND_HALF_UP);
            storeDeviceTypeVo.setPercentMeiTuanOutCoin(meiTuanOutCoinTotalRate.multiply(new BigDecimal("100")));

            //微信核销出币
            BigDecimal weiXinVerifyOutCoinTotal = new BigDecimal(storeDeviceTypeVo.getWeiXinVerifyTotalCoin());
            BigDecimal weiXinVerifyOutCoinTotalRate = weiXinVerifyOutCoinTotal.divide(total, 2, BigDecimal.ROUND_HALF_UP);
            storeDeviceTypeVo.setPercentWeiXinVerifyOutCoin(weiXinVerifyOutCoinTotalRate.multiply(new BigDecimal("100")));

        }
        log.info("线上投币{}：", storeDeviceTypeVo.getInsertCoinOnLine());
        log.info("线下投币{}：", storeDeviceTypeVo.getInsertCoinOffline());
        //投币情况
        if (storeDeviceTypeVo.getInsertCoinTotal() > 0) {
            BigDecimal total = new BigDecimal(storeDeviceTypeVo.getInsertCoinTotal());
            //线上投币
            BigDecimal insertCoinOnLine = new BigDecimal(storeDeviceTypeVo.getInsertCoinOnLine());
            BigDecimal insertCoinOnLineRate = insertCoinOnLine.divide(total, 2, BigDecimal.ROUND_HALF_UP);
            storeDeviceTypeVo.setPercentInsertCoinOnLine(insertCoinOnLineRate.multiply(new BigDecimal("100")));

            //线下投币
            BigDecimal insertCoinOffline = new BigDecimal(storeDeviceTypeVo.getInsertCoinOffline());
            BigDecimal insertCoinOfflineRate = insertCoinOffline.divide(total, 2, BigDecimal.ROUND_HALF_UP);
            storeDeviceTypeVo.setPercentInsertCoinOffline(insertCoinOfflineRate.multiply(new BigDecimal("100")));
        }

    }

    private List<StatsStoreDeviceTypeVo> findFromStatsStoreDeviceNo(StatsDeviceDto statsDeviceDto) {
        List<StatsStoreDeviceTypeVo> returnStatsStoreDeviceTypeList = new ArrayList<>();
        List<StatsStoreDeviceTypeVo> sumStatsDeviceVoByDeviceNoList = statsDeviceDao.findStatsDeviceNoSumByMchStoreId(statsDeviceDto);
        // 使用Map集合可以避免双重循环提高效率
        Map<String, StatsStoreDeviceTypeVo> statsStoreDeviceTypeVoMap = sumStatsDeviceVoByDeviceNoList.stream().collect(Collectors.toMap(StatsStoreDeviceTypeVo::getDeviceNo, v -> v));
        for (DeviceVo deviceVo : statsDeviceDto.getDeviceVoList()) {
            log.info("设备编号{}：", deviceVo.getDeviceNo());
            StatsStoreDeviceTypeVo storeDeviceTypeVo = statsStoreDeviceTypeVoMap.get(deviceVo.getDeviceNo());
            if (ObjectUtils.isEmpty(storeDeviceTypeVo)) {
                //初始化数据
                storeDeviceTypeVo = new StatsStoreDeviceTypeVo();
                this.initStoreDeviceTypeData(storeDeviceTypeVo);
            }
            //售货机默认值
            storeDeviceTypeVo.setTotalQuantity(0);

            storeDeviceTypeVo.setDeviceNo(deviceVo.getDeviceNo());
            storeDeviceTypeVo.setAlias(deviceVo.getAlias());
            storeDeviceTypeVo.setDeviceTypeName(deviceVo.getDeviceTypeName());
            storeDeviceTypeVo.setDeviceTypeId(deviceVo.getDeviceTypeId());

            storeDeviceTypeVo.setActivityTurnover(storeDeviceTypeVo.getSeckillMoney()
                    .add(storeDeviceTypeVo.getGroupBookingMoney())
                    .add(storeDeviceTypeVo.getConsumptionOfRedEnvelopesMoney())
                    .add(storeDeviceTypeVo.getMemberOfTheStoredValueMoney()));
            storeDeviceTypeVo.setScanCodePayTotalTurnover(storeDeviceTypeVo.getTurnoverOnLine());
            storeDeviceTypeVo.setTurnoverMeiTuan(storeDeviceTypeVo.getTurnoverMeiTuan());
            storeDeviceTypeVo.setTurnoverDouYin(storeDeviceTypeVo.getTurnoverDouYin());
            storeDeviceTypeVo.setCashMoney(storeDeviceTypeVo.getCashMoney());
            storeDeviceTypeVo.setGiftConsume(storeDeviceTypeVo.getGiftConsume());
            storeDeviceTypeVo.setOnLinePayOutCoinTotal(storeDeviceTypeVo.getOnLinePayOutCoinTotal());
            storeDeviceTypeVo.setOffLinePayOutCoinTotal(storeDeviceTypeVo.getOffLinePayOutCoinTotal());
            storeDeviceTypeVo.setDouYinOutCoinTotal(storeDeviceTypeVo.getDouYinOutCoinTotal());
            storeDeviceTypeVo.setMeiTuanOutCoinTotal(storeDeviceTypeVo.getMeiTuanOutCoinTotal());
            storeDeviceTypeVo.setFetchMemberOutCoinTotal(storeDeviceTypeVo.getFetchMemberOutCoinTotal());
            storeDeviceTypeVo.setWeiXinVerifyTotalCoin(storeDeviceTypeVo.getWeiXinVerifyTotalCoin());

            //售货机统计出货数量
            if (storeDeviceTypeVo.getDeviceTypeId().compareTo(DeviceTypeEnum.VENDING_MACHINE.getCode()) == 0 ||
                    storeDeviceTypeVo.getDeviceTypeId().compareTo(DeviceTypeEnum.SCREEN_VENDING_MACHINE.getCode()) == 0 ||
                    storeDeviceTypeVo.getDeviceTypeId().compareTo(DeviceTypeEnum.OPEN_DOOR_VENDING_MACHINE.getCode()) == 0) {
                statsDeviceDto.setDeviceId(storeDeviceTypeVo.getDeviceId());
                statsDeviceDto.setSecondaryType(CommodityStockRecordSecondTypeEnum.VENDING_MACHINE_OUT.getCode());
                statsDeviceDto.setFirstType(CommodityStockRecordFirstTypeEnum.OUTBOUND.getCode());
                StatsDeviceVo statsDeviceVo = statsCommodityStockRecordService.findStatsCommodityStockRecordDevice(statsDeviceDto);
                storeDeviceTypeVo.setTotalQuantity(statsDeviceVo.getTotalQuantity());
            }
            if ((statsDeviceDto.getDayType() <= 1 || statsDeviceDto.getDayType() == 4) &&
                    !statsDeviceDto.getEndDateStr().equals(DateTimeUtils.getCurrentDateStr())) {
                this.outConDevicePercent(storeDeviceTypeVo);
            }
            returnStatsStoreDeviceTypeList.add(storeDeviceTypeVo);
        }
        return returnStatsStoreDeviceTypeList;
    }

    private void initStoreDeviceTypeData(StatsStoreDeviceTypeVo storeDeviceTypeVo) {
        storeDeviceTypeVo.setTurnover(BigDecimal.valueOf(0));
        storeDeviceTypeVo.setSettlementMoney(BigDecimal.valueOf(0));
        storeDeviceTypeVo.setCashMoney(BigDecimal.valueOf(0));
        storeDeviceTypeVo.setTurnoverOnLine(BigDecimal.valueOf(0));
        storeDeviceTypeVo.setActivityTurnover(BigDecimal.valueOf(0));
        storeDeviceTypeVo.setOutCoinTotal(0);
        storeDeviceTypeVo.setOnLineOutCoinTotal(0);
        storeDeviceTypeVo.setOnLinePayOutCoinTotal(0);
        storeDeviceTypeVo.setOffLinePayOutCoinTotal(0);
        storeDeviceTypeVo.setInsertCoinTotal(0);
        storeDeviceTypeVo.setInsertCoinOnLine(0);
        storeDeviceTypeVo.setInsertCoinOffline(0);
        storeDeviceTypeVo.setGiftConsume(0);
        storeDeviceTypeVo.setGiftCost(BigDecimal.valueOf(0));
        storeDeviceTypeVo.setGiftOutRate(BigDecimal.valueOf(0));
        storeDeviceTypeVo.setTurnoverDouYin(BigDecimal.valueOf(0));
        storeDeviceTypeVo.setTurnoverMeiTuan(BigDecimal.valueOf(0));
        storeDeviceTypeVo.setFetchMemberOutCoinTotal(0);
        storeDeviceTypeVo.setMeiTuanOutCoinTotal(0);
        storeDeviceTypeVo.setTotalQuantity(0);
        storeDeviceTypeVo.setDouYinOutCoinTotal(0);
        storeDeviceTypeVo.setWeiXinVerifyTotalCoin(0);
        storeDeviceTypeVo.setWeiXinSeckillOutCoinTotal(0);
        storeDeviceTypeVo.setWeiXinGroupBuyingOutCoinTotal(0);
        storeDeviceTypeVo.setWeiXinVoucherOutCoinTotal(0);
        storeDeviceTypeVo.setArtificialOutCoinTotal(0);
        storeDeviceTypeVo.setGameCoinRedPacketCoinTotal(0);
        storeDeviceTypeVo.setGroupBenefitCoinTotal(0);
        storeDeviceTypeVo.setDistributeBenefitCoinTotal(0);
        storeDeviceTypeVo.setQuantityOfCoinsSold(0);
        storeDeviceTypeVo.setAmountOfCoinsConsumed(0);
        storeDeviceTypeVo.setRemainingCoins(0);
        storeDeviceTypeVo.setAverageCoinPrice(BigDecimal.ZERO);
        storeDeviceTypeVo.setTurnoverGameCoin(BigDecimal.ZERO);
        storeDeviceTypeVo.setScanCodePayTotalTurnover(BigDecimal.ZERO);
        storeDeviceTypeVo.setScanningFee(BigDecimal.ZERO);
        storeDeviceTypeVo.setTiktokCancellationFee(BigDecimal.ZERO);
        storeDeviceTypeVo.setMeiTuanCancellationFee(BigDecimal.ZERO);
        storeDeviceTypeVo.setSeckillMoney(BigDecimal.ZERO);
        storeDeviceTypeVo.setGroupBookingMoney(BigDecimal.ZERO);
        storeDeviceTypeVo.setConsumptionOfRedEnvelopesMoney(BigDecimal.ZERO);
        storeDeviceTypeVo.setMemberOfTheStoredValueMoney(BigDecimal.ZERO);
    }

    /**
     * 当天
     */
    private List<StatsStoreDeviceTypeVo> findTodayStatsDeviceStoreFromOrder(StatsDeviceDto statsDeviceDto) {
        statsDeviceDto.setStartDateStr(DateTimeUtils.getTodayStartTime());
        statsDeviceDto.setEndDateStr(DateTimeUtils.getTodayEndTime());
        List<StatsStoreDeviceTypeVo> statsStoreDeviceTypeVoList = statsStoreDeviceTypeService.findOrderStatisticsGroupByDeviceType(statsDeviceDto);
        return statsStoreDeviceTypeVoList;
    }
}
